package bank;

import java.util.ArrayList;
import java.util.Date;

public abstract class Konto {

	/**
	 * @uml.property name="Kontonummer"
	 */
	private int kontonummer;
	/**
	 * @uml.property name="SPARKONTO" readOnly="true"
	 */
	public static final int SPARKONTO = 0;
	/**
	 * @uml.property name="GIROKONTO" readOnly="true"
	 */
	public static final int GIROKONTO = 1;

	/**
	 * @uml.property name="kontostand"
	 */
	private double kontostand;
	/**
	 * @uml.property name="meineKontobewegungen"
	 * @uml.associationEnd multiplicity="(0 -1)" ordering="true"
	 *                     aggregation="composite"
	 *                     inverse="konto:bank.Kontobewegung"
	 */
	private ArrayList<Kontobewegung> meineKontobewegungen;

	public Konto() {
	}
	public Konto(int kontonummer) {
		meineKontobewegungen = new ArrayList<Kontobewegung>();
		setKontonummer(kontonummer);
		setKontostand(0);
	}

	/**
	 * Getter of the property <tt>Kontonummer</tt>
	 *
	 * @return Returns the kontonummer.
	 * @uml.property name="Kontonummer"
	 */
	public int getKontonummer() {
		return kontonummer;
	}

	/**
	 * Setter of the property <tt>Kontonummer</tt>
	 *
	 * @param Kontonummer
	 *            The kontonummer to set.
	 * @uml.property name="Kontonummer"
	 */
	public void setKontonummer(int kontonummer) {
		this.kontonummer = kontonummer;
	}


	/**
	 * Getter of the property <tt>kontostand</tt>
	 *
	 * @return Returns the kontostand.
	 * @uml.property name="kontostand"
	 */
	public double getKontostand() {
		return kontostand;
	}

	/**
	 * Setter of the property <tt>kontostand</tt>
	 *
	 * @param kontostand
	 *            The kontostand to set.
	 * @uml.property name="kontostand"
	 */
	public void setKontostand(double kontostand) {
		this.kontostand = kontostand;
	}

    public void einzahlen(double aBetrag) {
        einzahlen(aBetrag, new Date());
    }

    public void einzahlen(double aBetrag, Date aDate) {
        setKontostand(getKontostand() + aBetrag);
        getMeineKontobewegungen().add(new Kontobewegung(aDate, aBetrag));
    }

    public void auszahlen(double aBetrag) throws Exception {
        auszahlen(aBetrag, new Date());
    }

    public void auszahlen(double aBetrag, Date aDate) throws Exception {
        setKontostand(getKontostand() - aBetrag);
        getMeineKontobewegungen().add(new Kontobewegung(aDate, -aBetrag));
    }

	/**
	 * Getter of the property <tt>meineKontobewegungen</tt>
	 *
	 * @return Returns the meineKontobewegungen.
	 * @uml.property name="meineKontobewegungen"
	 */
	public ArrayList<Kontobewegung> getMeineKontobewegungen() {
		return meineKontobewegungen;
	}

	public static Konto neuesKonto(int kontoNummer, int kontoArt) {
		switch (kontoArt) {
			case GIROKONTO:
				return new Girokonto(kontoNummer);
			case SPARKONTO:
				return new Sparkonto(kontoNummer);
		}
		throw new IllegalArgumentException("Falsche Kontoart: " + kontoArt);
	}
}
